package com.xh.easyretry.aop;

import com.xh.easyretry.RetryExecutor;
import com.xh.easyretry.annotations.XHRetry;
import com.xh.easyretry.common.result.BaseResult;
import com.xh.easyretry.common.result.CommonResultCode;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.stereotype.Component;

import java.util.Objects;


@Slf4j
@Aspect
@Component
public class XHRetryAspect implements BeanPostProcessor {

    @Autowired
    private RetryExecutor retryExecutor;


    @Around("@annotation(XHRetry)")
    public Object around(ProceedingJoinPoint pjp, XHRetry XHRetry) {
        try {
            Object result = pjp.proceed();
            if (Objects.isNull(result)) {
                return null;
            } else if (result instanceof BaseResult) {
                if (((BaseResult) result).isSuccess()) {
                    return result;
                }
                if (Objects.equals(((BaseResult) result).getCode(), CommonResultCode.NEED_RETRY_FAIL)) {
                    log.error("msg=首次调用失败，将进行重试");
                    return retryExecutor.doRetry(XHRetry.retryStrategy(), pjp);
                }
            }
            return result;
        } catch (Throwable e) {
            log.error("msg=首次调用异常，将进行重试", e);
            return retryExecutor.doRetry(XHRetry.retryStrategy(), pjp);
        }
    }
}
